#include "crc32verifier.h"
#include <QDebug>
#include <QtEndian>

bool CRC32Verifier::verify(const QByteArray &fullFrame)
{
    if (fullFrame.size() < 16) {
        qDebug() << "数据长度不足，无法提取CRC信息。";
        return false;
    }
    // 提取数据部分（去掉最后16字节）
    QByteArray dataPart = fullFrame.left(fullFrame.size() - 16);
    // 提取CRC字段（从dataPart.size()+8开始，共4字节）
    QByteArray crcBytes = fullFrame.mid(dataPart.size() + 8, 4);
    // 将接收到的CRC转换为quint32，并转为大端
    quint32 receivedCrc = 0;
    memcpy(&receivedCrc, crcBytes.constData(), 4);
    receivedCrc = qFromBigEndian<quint32>(receivedCrc);
    // 计算数据部分的CRC32
    quint32 calculatedCrc = calculate(dataPart);
    // 输出调试信息
    //qDebug() << "接收的 CRC32：" << QString("0x%1").arg(receivedCrc, 8, 16, QChar('0')).toUpper();
    //qDebug() << "计算的 CRC32：" << QString("0x%1").arg(calculatedCrc, 8, 16, QChar('0')).toUpper();

    // 校验结果
    if (receivedCrc == calculatedCrc) {
        //qDebug() << "CRC32 校验通过！";
        return true;
    } else {
        //qDebug() << "CRC32 校验失败！";
        return false;
    }
}

quint32 CRC32Verifier::calculate(const QByteArray& data)
{
    quint32 crc = 0xFFFFFFFF;
    const quint32 polynomial = 0xEDB88320;

    for (char ch : data) {
        quint8 byte = static_cast<quint8>(ch);
        crc ^= byte;
        for (int i = 0; i < 8; ++i) {
            if (crc & 1)
                crc = (crc >> 1) ^ polynomial;
            else
                crc >>= 1;
        }
    }
    return crc ^ 0xFFFFFFFF;
}
